import React, {useState, useEffect, useRef, useMemo, memo} from "react";
import PropTypes from "prop-types";
import CheckBox from "../CheckBox";

import './index.scss'

const Table = props => {

    // 状态
    const [checkedList, setCheckedList] = useState(new Array(props.data.length).fill(false))

    // ref
    const tableHeaderRef = useRef()
    const tableBodyRef = useRef()

    // 副作用
    useEffect(() => {
        tableHeaderRef.current.style.width = tableBodyRef.current.clientWidth + 'px'
        tableBodyRef.current.style.marginTop = (tableHeaderRef.current.clientHeight + 1) + 'px'
    }, [])

    useEffect(() => {
        setCheckedList(new Array(props.data.length).fill(false))
    }, [props.data])

    const selectTotal = useMemo(() => {
        return checkedList.reduce((previousValue, currentValue) => {
            return currentValue ? (previousValue+1) : previousValue
        }, 0)
    }, [checkedList])

    const select = index => {
        return () => {
            checkedList[index] = !checkedList[index]
            setCheckedList([...checkedList])
            props.select(checkedList.map((_, i) => props.data[i][props.keyName]).filter((_, i) => checkedList[i]))
        }
    }

    const selectAll = () => {

        setCheckedList([...checkedList.fill(selectTotal !== props.data.length)])
        props.select(checkedList.map((_, i) => props.data[i][props.keyName]).filter((_, i) => checkedList[i]))
    }

    return (
        <div style={{  ...props.style }}
             className={ 'table-warp ' + props.className }
        >
            <div ref={ tableHeaderRef } className={ 'table-header' }>
                <div className='row'>
                    {
                        props.selection
                            ? (
                                <div className='col check'>
                                    <CheckBox checked={ selectTotal === props.data.length }
                                              active={ selectTotal > 0 }
                                              onChange={ selectAll }
                                    />
                                </div>
                            )
                            : (<></>)
                    }
                    {
                        props.columns.map(col => {
                            return (
                                <div className='col'
                                     style={ col.width ? { justifyContent: col.align, width: col.width } : { justifyContent: col.align, flex: '1' } }
                                     key={ col.fieldName }
                                >
                                    { col.name }
                                </div>
                            )
                        })
                    }
                </div>
            </div>
            <div ref={ tableBodyRef } className='table-body'>
                {
                    props.data.map((item, index) => {
                        return (
                            <div className='row' key={ item[props.keyName] }>
                                {
                                    props.selection
                                        ? (
                                            <div className='col check'>
                                                <CheckBox checked={checkedList[index]} onChange={select(index)} />
                                            </div>
                                        )
                                        : (<></>)
                                }
                                {
                                    props.columns.map(col => {
                                        return (
                                            <div className='col'
                                                 style={ { justifyContent: col.align, ...(col.width ? {width: col.width} : {flex: '1'}) } }
                                                 key={ col.fieldName }
                                            >
                                                { col.render({ value: item[col.fieldName], list: props.data, index: index }) }
                                            </div> )
                                    })
                                }
                            </div>
                        )
                    })
                }
            </div>
        </div>
    )
}

Table.propTypes = {
    style: PropTypes.object,
    className: PropTypes.string,
    selection: PropTypes.bool,
    keyName: PropTypes.string,
    columns: PropTypes.array.isRequired,
    data: PropTypes.array,
    select: PropTypes.func
}

Table.defaultProps = {
    style: {},
    className: '',
    selection: false,
    keyName: 'id',
    data: [],
    select: () => {}
}

export default memo(Table)